home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Shareware Overload Trio 2
/
Shareware Overload Trio Volume 2 (Chestnut CD-ROM).ISO
/
dir43
/
med300.zip
/
MEFILE.CLA
< prev
next >
Wrap
Text File
|
1994-02-22
|
35KB
|
658 lines
!▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄
!█ █
!█ MEFILE.CLA █
!█ File handling functions █
!█ █
!█ Revision Number: 1 █
!█ Revision Date : 22-Feb-94 █
!█ █
!█ Revision History █
!█ 1 Created █
!█ █
!▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀
MEMBER('MEMOEDIT')
!─────────────────────────────────────────────────────────────────────────
! Local Module MAP
!─────────────────────────────────────────────────────────────────────────
MAP !
ME_LoadASCII( STRING ), BYTE ! Load file into document
ME_SaveASCII( STRING, USHORT, USHORT ), BYTE ! Save block to file
.
!─────────────────────────────────────────────────────────────────────────
! Local Module Data
!─────────────────────────────────────────────────────────────────────────
sFileName STRING(64) ! DOS file name
oFile FILE,PRE(OFI),NAME(sFileName),DRIVER('ASCII')
gRecord RECORD ! Generic DOS File
sLine STRING(255) !
. . !
!═════════════════════════════════════════════════════════════════════════
! Load ASCII file at current cursor position
!═════════════════════════════════════════════════════════════════════════
ME_LoadASCII FUNCTION( sName )
! Equates:
eLoadPartial EQUATE('File too big! Try to load anyway?')
! Locals:
isInsPos SHORT ! Insertion point
isTxtLen SHORT ! Text length
isOldLen SHORT ! Previous text length
CODE
sFileName = sName ! Get filename
OPEN(oFile) ! Open file
IF ERRORCODE() THEN RETURN( 0 ). !
IF BYTES(oFile) > (0.9 * (MED:usMaxChars - MED:usCharacters))
IF NOT ME_Confirm(eLoadPartial) ! If whole file only
CLOSE(oFile) ! Close file
RETURN( 0 ) ! Return
. . ! Endif
MED:bbHasChanged = 1 ! Set modified flag
isInsPos = MED:usPosition ! Set insertion point
isOldLen = 0 ! Clear old length
SET(oFile) ! Set to first line
LOOP WHILE NOT EOF(oFile) ! Loop for each file line
NEXT(oFile) ! Get file line
isTxtLen = LEN(CLIP(OFI:gRecord)) ! Calc line length
IF isInsPos + isTxtLen >= MED:usMaxChars ! If not enough roon
BREAK ! Break
. ! Endif
ME_InsTxt(isInsPos, isTxtLen, OFI:gRecord) ! Insert text
isInsPos += isTxtLen ! Move insertion point
CASE MEU:ubAscImpFmt ! ASCII Import type:
OF eImpRefNone ! Convert all CR's to
ME_InsTxt(isInsPos, 1, CHR(eHRt)) ! to hard returns
isInsPos += 1 !
OF eImpRefPart ! Convert 2 or more CR's
IF isTxtLen = 0 AND isOldLen = 0 ! to hard returns
ME_InsTxt(isInsPos, 1, CHR(eHRt)) !
ELSE !
ME_InsTxt(isInsPos, 1, CHR(' ')) !
. !
isInsPos += 1 !
OF eImpRefFull ! Ignore CR's completely
ME_InsTxt(isInsPos, 1, CHR(' ')) !
isInsPos += 1 !
. ! End case
isOldLen = isTxtLen ! Save old text length
. ! End loop
CLOSE(oFile) ! Close file
ME_ReformDoc() ! Reformat document
RETURN( 1 ) !
!═════════════════════════════════════════════════════════════════════════
! Save block range to ASCII text file
!═════════════════════════════════════════════════════════════════════════
ME_SaveASCII FUNCTION( sName, usRangeBegin, usRangeEnd )
! Return:
bbRetVal BYTE ! Status flag
! Locals:
isLine SHORT ! Line index
isLineStart SHORT ! Line start
isLineEnd SHORT ! Line end
isCodeNdx SHORT ! Code position
CODE
bbRetVal = 0 ! Clear return value
sFileName = sName ! Assign name
CREATE(oFile) ! Create new file
IF ERRORCODE() ! Check for errors
STOP(ERROR()) !
DO Quit !
. !
OPEN(oFile) ! Open the file
IF ERRORCODE() ! Check for errors
STOP(ERROR()) !
DO Quit !
. !
isLine = ME_LineIndex(usRangeBegin) ! Set initial values
isLineStart = usRangeBegin !
isLineEnd = ME_LineEnd(isLine) !
LOOP WHILE isLineEnd < usRangeEnd ! Loop until done
ME_GetBlock(OFI:sLine, isLineStart, (isLineEnd-isLineStart)+1)
DO WriteLine ! Write line to file
isLine += 1 !
isLineStart = ME_LineStart(isLine) !
isLineEnd = ME_LineEnd(isLine) !
. ! End loop
ME_GetBlock(OFI:sLine, isLineStart, (usRangeEnd-isLineStart)+1)
DO WriteLine ! Take care of last line
CLOSE(oFile) ! Close file
bbRetVal = 1 ! Set return value
DO Quit ! Quit
!──────────────────────────────────────────────────────────────────────────
Quit ROUTINE ! Common exit routine
!──────────────────────────────────────────────────────────────────────────
ME_SetPage() ! Redisplay page
ME_ShowPage() !
RETURN( bbRetVal )
!──────────────────────────────────────────────────────────────────────────
WriteLine ROUTINE ! Write line to disk
!──────────────────────────────────────────────────────────────────────────
CASE MEU:ubAscExpFmt ! Export format:
OF eExpKillCode ! Remove all format codes
isCodeNdx = INSTRING(CHR(eHRt), OFI:sLine) !
IF isCodeNdx !
OFI:sLine = SUB(OFI:sLine, 1, isCodeNdx-1)
. !
OF eExpKeepCode ! Keep format codes
! Nothing to do !
. !
ADD(oFile) ! Write to file
IF ERRORCODE() THEN STOP(ERROR()). !
!═════════════════════════════════════════════════════════════════════════
! File selection and drive/directory navigation
!═════════════════════════════════════════════════════════════════════════
ME_PickFile FUNCTION( sFileSpec )
! Return:
sRetVal STRING(64) ! Selected filename
! Screens:
ubRepNdx BYTE ! Repeat index
wScreen SCREEN(14,66),PRE(SCR),COLOR(112)
!dimensions=25,80,25,80
ROW(1,65) PAINT(1,2),TRN
ROW(2,65) PAINT(13,2),COLOR(8),TRN
ROW(14,1) PAINT(1,2),TRN
ROW(14,3) PAINT(1,62),COLOR(8),TRN
ROW(1,1) STRING('┌─{10}')
COL(55) STRING('─{9}┐')
ROW(13,1) STRING('└─{62}┘')
REPEAT(11)
ROW(2,1) STRING('│')
ROW(2,64) STRING('│')
.
ssPath ROW(1,13) STRING(41),COLOR(112)
REPEAT(10,4),EVERY(1,15),INDEX(ubRepNdx)
ROW(3,3) POINT(1,15),USE(?Point),COLOR(78)
ssName COL(4) STRING(13)
.
ssULArrow ROW(3,2) STRING(1),COLOR(126)
ssURArrow COL(63) STRING(1),COLOR(126)
ssLLArrow ROW(12,2) STRING(1),COLOR(126)
ssLRArrow COL(63) STRING(1),COLOR(126)
.
! Locals:
eRows EQUATE(10) ! Rows in scroll area
eCols EQUATE(4) ! Columns in scroll area
eDOSSubDir EQUATE(10H) ! DOS Sub-directory bit
eDOSVolLabel EQUATE(08H) ! DOS Volume label bit
qQueue QUEUE,PRE(QUE) ! Scroll table
sSlash STRING(1) ! Directory slash
sName STRING(8) ! File name
sExt STRING(3) ! File extension
.
gDOS1Dir GROUP,PRE(DOS) ! DOS1 LEM Set/NextDir group
BYTE,DIM(21) ! Reserved
ubAttrib BYTE ! File attribute
isTime SHORT ! File time
isDate SHORT ! File date
ilSize LONG ! File size in bytes
sNameExt STRING(13) ! Filename
. !
gRegisters GROUP ! CPU Registers
usAX USHORT !
usBX USHORT !
usCX USHORT !
usDX USHORT !
usSI USHORT !
usDI USHORT !
usCFlag USHORT !
usFlags USHORT !
. !
gSegRegs GROUP ! CPU Segment Registers
usES USHORT !
usCS USHORT !
usSS USHORT !
usDS USHORT !
. !
ilTopRow LONG ! Top row offset
ubRow BYTE ! Current screen row
ubSavNdx BYTE ! Saved repeat index
ubPeriod BYTE ! Location of '.' in name.ext
sPath STRING(64) ! Current file path
sSavedPath STRING(64) ! Saved file path
sCFileSpec CSTRING(65) ! ASCIIZ file sepc
ubFirstDrive BYTE(2) ! Lowest logical drive #
ubLastDrive BYTE ! Highest logical drive #
ubDefDrive BYTE ! Default drive #
ubDrive BYTE ! Drive #
CODE
sCFileSpec = sFileSpec ! Copy to ASCIIZ string
sSavedPath = PATH() ! Save current path
sPath = PATH() ! Set path variable
OPEN(wScreen) ! Open screen
SETCURSOR ! Hide cursor
DO GetDrives ! Get # of logical drives
DO BuildTable ! Build file list
DO FirstPage ! Display first page
ubRepNdx = (ubLastDrive - ubFirstDrive) + 1 !
LOOP ! Loop
DO Alerts ! Alert hot keys
SELECT(?Point) ! Get keystroke
ACCEPT !
CASE KEYCODE() ! Process keystroke
OF EnterKey; DO Select !
OF EscKey; sRetVal = ''; DO Quit !
OF UpKey; DO MoveUp !
OF DownKey; DO MoveDown !
OF PgUpKey; DO PageUp !
OF PgDnKey; DO PageDown !
OF CtrlPgUp; DO FirstPage !
OF CtrlPgDn; DO LastPage !
. . ! End loop
!──────────────────────────────────────────────────────────────────────────
Quit ROUTINE ! Clean up and exit function
!──────────────────────────────────────────────────────────────────────────
CLOSE(wScreen) ! Close screen
SETPATH(sSavedPath) ! Restore original path
FREE(qQueue) ! Free memory table
RETURN(sRetVal) ! Return filename
!──────────────────────────────────────────────────────────────────────────
Alerts ROUTINE ! Alert hot keys
!──────────────────────────────────────────────────────────────────────────
ALERT !
ALERT(EscKey) !
ALERT(DownKey) !
ALERT(UpKey) !
ALERT(PgUpKey) !
ALERT(PgDnKey) !
ALERT(CtrlPgUp) !
ALERT(CtrlPgDn) !
!──────────────────────────────────────────────────────────────────────────
Select ROUTINE ! Process the Enter key
!──────────────────────────────────────────────────────────────────────────
GET(qQueue, ilTopRow + ubRepNdx) ! Get file list entry
IF QUE:sSlash >= 'A' AND QUE:sSlash <= 'Z' ! If it's a drive
sPath = QUE:sSlash & ':\' ! Change to new drive
SETPATH(CLIP(sPath)) !
DO BuildTable ! Build new file list
DO FirstPage !
ubRepNdx = (ubLastDrive - ubFirstDrive) + 1 !
ELSIF QUE:sSlash = '\' ! Else if it's a directory
IF LEN(CLIP(PATH())) = 3 ! If it's the root
sPath = CLIP(PATH()) & CLIP(QUE:sName) ! No backslash needed
ELSE ! Else
sPath = CLIP(PATH()) & '\' & CLIP(QUE:sName)! Append a backslash
. ! Endif
IF QUE:sExt ! If there is an extension
sPath = CLIP(sPath) & '.' & QUE:sExt ! Append that also
. ! Endif
SETPATH(CLIP(sPath)) ! Change to new directory
sPath = CLIP(sPath) & '\' ! Append a slash
DO BuildTable ! Build new file list
DO FirstPage !
ubRepNdx = (ubLastDrive - ubFirstDrive) + 1 !
ELSE ! Else
IF LEN(CLIP(PATH())) = 3 ! If it's the root
sRetVal = CLIP(PATH()) & CLIP(QUE:sName) | ! Return filename
& '.' & CLIP(QUE:sExt) ! Else
ELSE ! Return filename
sRetVal = CLIP(PATH()) & '\' & CLIP(QUE:sName) |
& '.' & CLIP(QUE:sExt) ! Endif
. !
DO Quit ! Quit function
. ! Endif
!──────────────────────────────────────────────────────────────────────────
MoveUp ROUTINE ! Move up one line
!──────────────────────────────────────────────────────────────────────────
IF ubRepNdx > 1 !
ubRepNdx -= 1 !
ELSIF ilTopRow > 1 !
ilTopRow -= 1 !
DO ShowTable !
ELSE !
BEEP !
. !
!──────────────────────────────────────────────────────────────────────────
MoveDown ROUTINE ! Move down one line
!──────────────────────────────────────────────────────────────────────────
IF ilTopRow + ubRepNdx < RECORDS(qQueue) !
IF ubRepNdx < eRows * eCols !
ubRepNdx += 1 !
ELSE !
ilTopRow += 1 !
DO ShowTable !
. !
ELSE !
BEEP !
. !
!──────────────────────────────────────────────────────────────────────────
PageUp ROUTINE ! Move to previous page
!──────────────────────────────────────────────────────────────────────────
IF (ubRepNdx-1) % eRows !
ubRepNdx -= (ubRepNdx-1) % eRows !
ELSIF ilTopRow >= eRows * eCols !
ilTopRow -= eRows * eCols !
DO ShowTable !
ELSE !
BEEP !
. !
!
!──────────────────────────────────────────────────────────────────────────
PageDown ROUTINE ! Move to next page
!──────────────────────────────────────────────────────────────────────────
IF (ubRepNdx % eRows) > 0 !
ubRepNdx += eRows !
ubRepNdx -= (ubRepNdx % eRows) !
ELSIF ilTopRow + eRows * eCols < RECORDS(qQueue)
ilTopRow += eRows * eCols !
DO ShowTable !
ELSE !
BEEP !
. !
!──────────────────────────────────────────────────────────────────────────
FirstPage ROUTINE ! Move to first page
!──────────────────────────────────────────────────────────────────────────
ilTopRow = 0 !
ubRepNdx = 1 !
DO ShowTable !
!──────────────────────────────────────────────────────────────────────────
LastPage ROUTINE ! Move to last page
!──────────────────────────────────────────────────────────────────────────
ubRepNdx = eRows !
ilTopRow = RECORDS(qQueue) - eRows * eCols !
IF ilTopRow < 0 !
ilTopRow = 0 !
ubRepNdx = RECORDS(qQueue) !
. !
DO ShowTable !
!──────────────────────────────────────────────────────────────────────────
ShowTable ROUTINE ! Display file list
!──────────────────────────────────────────────────────────────────────────
ubSavNdx = ubRepNdx !
LOOP ubRepNdx = 1 TO eRows * eCols !
CLEAR(qQueue) !
GET(qQueue, ilTopRow + ubRepNdx) !
IF QUE:sSlash >= 'A' AND QUE:sSlash <= 'Z' !
SCR:ssName = '[Drive ' & QUE:sSlash & ']' !
ELSE !
IF QUE:sExt !
SCR:ssName = QUE:sSlash & CLIP(QUE:sName) & '.' & QUE:sExt
ELSE !
SCR:ssName = QUE:sSlash & QUE:sName !
. . . !
ubRepNdx = ubSavNdx !
DO Arrows !
!──────────────────────────────────────────────────────────────────────────
BuildTable ROUTINE ! Build file list
!──────────────────────────────────────────────────────────────────────────
FREE(qQueue) !
LOOP ubDrive = ubFirstDrive TO ubLastDrive-1 !
CLEAR(qQueue) !
QUE:sSlash = CHR(VAL('A') + ubDrive) !
ADD(qQueue) !
. !
IF FindFirst(sCFileSpec, gDOS1Dir, 10h) = -1 THEN EXIT.
LOOP !
IF FindNext(gDOS1Dir) = -1 THEN BREAK. !
IF DOS:sNameExt = '.' OR BAND(DOS:ubAttrib, eDOSVolLabel) THEN CYCLE.
DO AddRecord !
. !
SORT(qQueue, QUE:sExt ) !
SORT(qQueue, QUE:sName ) !
SORT(qQueue, QUE:sSlash) !
SCR:ssPath = sPath !
!──────────────────────────────────────────────────────────────────────────
AddRecord ROUTINE ! Add record to file list
!──────────────────────────────────────────────────────────────────────────
CLEAR(qQueue) !
IF BAND(DOS:ubAttrib, eDOSSubDir) ! If entry is a directory
QUE:sSlash = '\' ! Display a slash
ELSE ! Else
QUE:sSlash = '<255>' ! A blank
. ! .
IF DOS:sNameExt = '..' ! If parent directory
QUE:sName = DOS:sNameExt ! Need name only
ELSE ! Else
ubPeriod = INSTRING('.', DOS:sNameExt, 1) ! Seperate name & extension
IF ubPeriod !
QUE:sName = SUB(DOS:sNameExt, 1, ubPeriod-1)
QUE:sExt = SUB(DOS:sNameExt, ubPeriod+1, 3)
ELSE !
QUE:sName = DOS:sNameExt !
. . ! Endif
ADD(qQueue) ! Add to table
!──────────────────────────────────────────────────────────────────────────
Arrows ROUTINE ! Display table scroll arrows
!──────────────────────────────────────────────────────────────────────────
SCR:ssULArrow = ' ' !
SCR:ssLLArrow = ' ' !
IF ilTopRow > 0 !
SCR:ssULArrow = '' !
.
IF ilTopRow + eRows * eCols < RECORDS(qQueue) !
SCR:ssLLArrow = '' !
. !
SCR:ssURArrow = SCR:ssULArrow !
SCR:ssLRArrow = SCR:ssLLArrow !
!──────────────────────────────────────────────────────────────────────────
GetDrives ROUTINE ! Get # of logical drives
!──────────────────────────────────────────────────────────────────────────
CLEAR(gRegisters) ! Save default drive #
usAX = 1900H !
Junk# = Int86X(21H, gRegisters, gRegisters, gSegRegs)
ubDefDrive = BAND(usAX, 0FFH) !
ubLastDrive = 0 ! Zero drive count
LOOP ! Loop
ubLastDrive += 1 ! Increment drive count
usDX = ubLastDrive ! Set as default drive
usAX = 0E00H !
Junk# = Int86x(21H, gRegisters, gRegisters, gSegRegs)
usAX = 1900H ! Get new current drive
Junk# = Int86x(21H, gRegisters, gRegisters, gSegRegs)
IF BAND(usAX, 0FH) <> ubLastDrive THEN BREAK.! Break if not the same
. ! End loop
usDX = ubDefDrive ! Set back to default drive
usAX = 0E00H !
Junk# = Int86x(21H, gRegisters, gRegisters, gSegRegs)
!═════════════════════════════════════════════════════════════════════════
! Paste text file at current cursor location
!═════════════════════════════════════════════════════════════════════════
ME_PasteFile PROCEDURE
CODE
sFileName = ME_PickFile('*.*') ! Get filename
IF NOT sFilename THEN RETURN. !
Junk# = ME_LoadASCII( sFileName ) ! Load file
RETURN
!═════════════════════════════════════════════════════════════════════════
! Copy marked block to text file
!═════════════════════════════════════════════════════════════════════════
ME_Copy2File PROCEDURE
! Equates:
eSaveTo EQUATE('Save block to text file:' )
eOverwrite EQUATE('Overwrite existing ' )
eFileSaved EQUATE('Marked block saved to disk')
! Locals:
bbQuit BYTE ! Quit flag
sMessage STRING(80) ! Message line
CODE
IF NOT MED:bbBlockShow THEN RETURN. ! Return if no block
DO GetFileName ! Get file name
ME_NormBlock() ! Save to file
IF ME_SaveASCII(sFileName, MED:isBlockBegin, MED:isBlockEnd)
OPEN(wStatus) ! Display completion message
MES:ssStatus = CENTER(eFileSaved, SIZE(MES:ssStatus))
ASK ! Wait for keypress
MEG:isKeyBuffer = KEYCODE() ! Save in buffer
CLOSE(wStatus) ! Close status screen
. ! Endif
DO Quit !
!──────────────────────────────────────────────────────────────────────────
Quit ROUTINE ! Common exit routine
!──────────────────────────────────────────────────────────────────────────
ME_MarkOff() ! Turn off block marking
MED:bbBlockShow = 0 !
ME_SetPage() !
ME_ShowPage() !
RETURN !
!──────────────────────────────────────────────────────────────────────────
GetFileName ROUTINE ! Get output file name
!──────────────────────────────────────────────────────────────────────────
bbQuit = 0 ! Clear quit flag
LOOP ! Loop
sFileName = ME_Entry(eSaveTo) ! Get file name
IF NOT sFileName ! If no file name
DO Quit ! Quit
ELSE ! Else
OPEN(oFile) ! Open file
IF NOT ERRORCODE() ! If file already exists
CLOSE(oFile) ! Ask user to confirm
IF NOT ME_Confirm(eOverwrite & CLIP(UPPER(sFileName)) & '?', 0) THEN CYCLE.
. ! Endif
BREAK ! Break
. . ! End loop
!═════════════════════════════════════════════════════════════════════════
! Edit an ASCII file
!═════════════════════════════════════════════════════════════════════════
ME_EditFile PROCEDURE( sName, usBufSize )
! Equates:
eDefAlloc EQUATE(4096) ! Default edit buffer size
eNotFound EQUATE('File not found. Create?') !
eLoadPartial EQUATE('File too big! Try to load anyway?')
eLoseChanges EQUATE('Lose changes?') !
! Editing screen:
wScreen SCREEN(25,80),PRE(SCR),AT(1,1),COLOR(27)
!dimensions=25,80,25,80
.
CODE
DO Init ! Initialize
DO LoadFile ! Load file
DO Edit ! Edit the file
DO Quit ! Clean-up and exit
!──────────────────────────────────────────────────────────────────────────
Init ROUTINE ! Initialize the edit buffer
!──────────────────────────────────────────────────────────────────────────
IF OMITTED(2) THEN usBufSize = 0. ! Set default value
usBufSize = ME_Max(usBufSize, eDefAlloc) ! Set edit buffer size
OPEN(wScreen) ! Open screen
IF MED:ulEditBuffer ! If current context
ADD(qDocument, 1) ! Save current context
. ! Endif
CLEAR(qDocument) ! Clear context
MED:bbAllocFlag = 1 ! Set allocation flag
MED:ulEditBuffer = CMalloc(usBufSize) ! Allocate buffer
IF NOT MED:ulEditBuffer ! If no memory
STOP('INSUFFICIENT MEMORY TO EDIT FILE') ! Warn user
DO Quit ! and quit
ELSE ! Else
MED:usMaxChars = usBufSize ! Set edit buffer size
. ! Endif
CMemSet(MED:ulEditBuffer, 20H, MED:usMaxChars) ! Clear buffer
ME_ScrnDefs(ROW(wScreen), COL(wScreen), ROWS(wScreen)-1, COLS(wScreen))
!──────────────────────────────────────────────────────────────────────────
LoadFile ROUTINE ! Load file into edit buffer
!──────────────────────────────────────────────────────────────────────────
sFileName = sName ! Assign name
OPEN(oFile) ! Open file
IF ERRORCODE() ! If not found
IF NOT ME_Confirm(eNotFound) THEN DO Quit. ! Ask to create
ELSE ! Else
IF BYTES(oFile) > 0.9 * MED:usMaxChars ! If can't load whole file
IF NOT ME_Confirm(eLoadPartial) ! If whole file only
CLOSE(oFile) ! Close file
DO Quit ! Quit
. . ! Endif
CLOSE(oFile) ! Close file
ME_ReformDoc() ! Initialize buffer
IF NOT ME_LoadASCII(sFileName) THEN DO Quit. ! Load file contents
. ! Endif
MED:bbHasChanged = 0 ! Clear changed flag
!──────────────────────────────────────────────────────────────────────────
Edit ROUTINE ! Edit the file
!──────────────────────────────────────────────────────────────────────────
LOOP ! Loop
ALERT ! Alert completion keys
ALERT(MEU:isFlSaveKey) !
ALERT(MEU:isFlCancKey) !
ME_Edit() ! Edit the file
CASE KEYCODE() ! Process keystrokes
OF MEU:isFlCancKey ! Cancel
IF MED:bbHasChanged !
IF NOT ME_Confirm(eLoseChanges, 0) !
CYCLE !
. . !
BREAK !
OF MEU:isFlSaveKey ! Save
DO SaveFile !
BREAK !
. . ! End loop
DO Quit ! Clean-up and exit
!──────────────────────────────────────────────────────────────────────────
SaveFile ROUTINE ! Save edit buffer to file and quit
!──────────────────────────────────────────────────────────────────────────
Junk# = ME_SaveASCII(sName, 0, MED:usCharacters-1)
!──────────────────────────────────────────────────────────────────────────
Quit ROUTINE ! Common exit code
!──────────────────────────────────────────────────────────────────────────
ME_Done() ! Deallocate memory
CLOSE(wScreen) ! Close screen
RETURN